package cc.shacocloud.luanniao.core.service.impl

import cc.shacocloud.luanniao.core.model.constant.KnowledgeBaseTypeEnum
import cc.shacocloud.luanniao.core.model.dto.input.KnowledgeBaseInput
import cc.shacocloud.luanniao.core.model.dto.input.KnowledgeBaseListInput
import cc.shacocloud.luanniao.core.model.mo.UserNamespaceMo
import cc.shacocloud.luanniao.core.model.po.KnowledgeBasePo
import cc.shacocloud.luanniao.core.repository.KnowledgeBaseRepository
import cc.shacocloud.luanniao.core.service.KnowledgeBaseService
import cc.shacocloud.luanniao.core.utils.QueryExpand
import cc.shacocloud.luanniao.core.utils.QueryExpand.pageQuery
import kotlinx.coroutines.reactor.awaitSingle
import org.springframework.data.domain.Page
import org.springframework.data.relational.core.query.Criteria
import org.springframework.stereotype.Service

/**
 * 知识库的默认实现
 * @author 思追(shaco)
 */
@Service
class KnowledgeBaseServiceImpl(
    val knowledgeBaseRepository: KnowledgeBaseRepository,
) : KnowledgeBaseService {

    /**
     * 知识库列表
     */
    override suspend fun list(input: KnowledgeBaseListInput, userNamespaceMo: UserNamespaceMo): Page<KnowledgeBasePo> {

        val namespaceCriteria = Criteria.where("namespaceId").`is`(requireNotNull(userNamespaceMo.namespace.id))
        val keywordCriteria = input.keyword?.let { Criteria.where("name").like("%$it%") }
        val parentIdCriteria = input.parentId?.let { Criteria.where("parentId").`is`(it) }

        return knowledgeBaseRepository.pageQuery(
            criteria = QueryExpand.and(namespaceCriteria, keywordCriteria, parentIdCriteria),
            pageable = input.toPageable()
        )
    }

    /**
     * 创建知识库
     */
    override suspend fun create(input: KnowledgeBaseInput, userNamespaceMo: UserNamespaceMo): KnowledgeBasePo {
        val user = userNamespaceMo.user
        val namespacePo = userNamespaceMo.namespace
        val knowledgeBasePo = KnowledgeBasePo(
            name = input.name,
            type = KnowledgeBaseTypeEnum.KNOWLEDGE_BASE,
            avatar = input.avatar,
            description = input.description,
            parentId = input.parentId,
            creatorId = requireNotNull(user.id),
            aiModelId = input.aiModelId,
            namespaceId = requireNotNull(namespacePo.id)
        )
        return knowledgeBaseRepository.save(knowledgeBasePo).awaitSingle()
    }

}